package com.seeyon.apps.brwh.service;

import com.alibaba.fastjson.JSONObject;
import com.seeyon.apps.brwh.kit.DBKit;
import com.seeyon.apps.brwh.kit.StrKit;
import com.seeyon.apps.brwh.manager.SencondDatailManager;
import com.seeyon.apps.brwh.po.SencondDatailPO;
import com.seeyon.cap4.form.bean.*;
import com.seeyon.cap4.form.service.CAP4FormManager;
import com.seeyon.ctp.common.AppContext;
import com.seeyon.ctp.common.ctpenumnew.manager.EnumManager;
import com.seeyon.ctp.common.exceptions.BusinessException;
import com.seeyon.ctp.common.log.CtpLogFactory;
import com.seeyon.ctp.organization.manager.OrgManager;
import com.seeyon.ctp.util.DBAgent;
import org.apache.commons.logging.Log;
import www.seeyon.com.utils.UUIDUtil;

import java.io.File;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

/**
 * 二级明细扩展Service
 */
public class SencondDatailService {
    private static final Log log = CtpLogFactory.getLog(SencondDatailService.class);

    private EnumManager enumManagerNew = (EnumManager) AppContext.getBean("enumManagerNew");
    private OrgManager orgManager = (OrgManager)AppContext.getBean("orgManager");
    private CAP4FormManager cap4FormManager = (CAP4FormManager) AppContext.getBean("cap4FormManager");

    private SencondDatailManager sencondDatailManager = (SencondDatailManager) AppContext.getBean("sencondDatailManager");

    //表头展示格式：title：表头名称【显示名称-对应key-是否表单枚举字段】
//    private static String fieldListString =  "[{\"title\":\"供应商名称-gysname-0\",\"dataField\":\"field0035\",\"writeBackField\":\"field0006\"},{\"title\":\"供应商编码-gyscode-0\",\"dataField\":\"field0166\",\"writeBackField\":\"field0007\"},{\"title\":\"供应商评级-gyspj-1\",\"dataField\":\"field0105\",\"writeBackField\":\"field0008\"},{\"title\":\"供应商类型-gyslx-0\",\"dataField\":\"field0264\",\"writeBackField\":\"field0009\"},{\"title\":\"历史合同评价-lshtpj-0\",\"dataField\":\"field0273\",\"writeBackField\":\"field0011\"},{\"title\":\"备注-bz-0\",\"dataField\":\"field0274\",\"writeBackField\":\"field0012\"}]";

    /**
     * 获取需要展示的列表头
     * @return
     */
    public List<Map<String,Object>> getTitleList(){
        List<Map<String,Object>> titleList = new ArrayList<Map<String,Object>>();
        //添加id
        HashMap<String, Object> titleMapId = new HashMap<>();
        titleMapId.put("field","id");
        titleMapId.put("title","ID");
        titleMapId.put("hide",true);
        titleList.add(titleMapId);
        //获取字段配置信息
        Map<String, Object> configSecondDetil = getConfigSecondDetil();
        List<Map<String,Object>> fieldList = (List<Map<String,Object>>)configSecondDetil.get("fieldListString");
        for (Map<String, Object> fidMap : fieldList) {
            String[] title = StrKit.str(fidMap.get("title")).split("-");
            HashMap<String, Object> titleMap = new HashMap<>();
            titleMap.put("field",title[1]);
            titleMap.put("title",title[0]);
            if(title[2].equals("1")){
                titleMap.put("hide",true);
                //新增名称列
                HashMap<String, Object> titleNameMap = new HashMap<>();
                titleNameMap.put("field",title[1]+"_name");
                titleNameMap.put("title",title[0]);
                titleList.add(titleNameMap);
            }
            titleList.add(titleMap);
        }

        return titleList;
    }


    /**
     * 获取列表数据信息
     * @param parm
     * @return
     */
    public List<Map<String,Object>> getDataList(Map<String,Object> parm){
        List<Map<String, Object>> reualList = new ArrayList<>();
        //获取字段配置信息
        Map<String, Object> configSecondDetil = getConfigSecondDetil();
        List<Map<String,Object>> fieldList = (List<Map<String,Object>>)configSecondDetil.get("fieldListString");
        //获取扩展查询数据字段
        List<Map<String,Object>> extendFieldQueryList = (List<Map<String,Object>>)configSecondDetil.get("extendFieldQuery");

        //将扩展查询的字段添加到查询列表中去
        if(null != extendFieldQueryList && !extendFieldQueryList.isEmpty()){
            for (Map<String, Object> map : extendFieldQueryList) {
                //判断字段中是否已经存在扩展列表中的字段
                List<Map<String, Object>> collect = fieldList.stream().filter(f -> StrKit.str(f.get("dataField")).equals(StrKit.str(map.get("dataField")))).collect(Collectors.toList());
                if(collect.isEmpty()){
                    fieldList.add(map);
                }
            }
        }

        String tempCode = StrKit.str(configSecondDetil.get("querTmepCode"));
        FormBean formBean = null;
        //获取字段配置信息
        try {
            formBean = cap4FormManager.getFormByFormCode(tempCode);
        } catch (BusinessException e) {
            log.info("二级明细扩展，获取选择列表数据表，根据模板编号获取表异常：",e);
            return reualList;
        }
        if(formBean != null){
            //获取多表数据id
            List<String> unquidStr = new ArrayList<>();

            //获取明细表单查询结构
            Map<String,List<String>> querFieldMapList = new HashMap<>();
            int tableIndex = 1;
            List<String> oldTableNameList = new ArrayList<>();
            for (Map<String, Object> fidMap : fieldList) {
                String dataField = StrKit.str(fidMap.get("dataField"));
                String title = StrKit.str(fidMap.get("title"));
                String[] titleSp = title.split("-");
                FormFieldBean formFieldBean = formBean.getFieldBeanByName(dataField);
                String ownerTableName = formFieldBean.getOwnerTableName();

                if(!oldTableNameList.contains(ownerTableName)){
                    oldTableNameList.add(ownerTableName);
                    tableIndex++;
                }
                //添加表单查询字段
                String bmOwnerTableName = ownerTableName + " tb"+tableIndex;
                if(!querFieldMapList.keySet().isEmpty()){
                    List<String> collect = querFieldMapList.keySet().stream().filter(q -> q.split(" ")[0].equals(ownerTableName)).collect(Collectors.toList());
                    if(!collect.isEmpty()){
                        bmOwnerTableName = collect.get(0);
//                        tableIndex--;
                    }
                    List<String> queryFieldList = querFieldMapList.get(bmOwnerTableName);

                    String bm = bmOwnerTableName.split(" ")[1];

                    if(null == queryFieldList || queryFieldList.isEmpty()){
                        queryFieldList = new ArrayList<String>();
                        //添加id
//                        if(tableName.equals(ownerTableName)){
                            queryFieldList.add(bm+".id "+bm+"id");
                        unquidStr.add(bm+"id");
//                        }
                        if(titleSp[2].equals("1")){
//                            queryFieldList.add("ct"+tableIndex+".SHOWVALUE "+dataField+"_name"+"- left join ctp_enum_item ct"+tableIndex+" on ct"+tableIndex+".ID = tb"+tableIndex+"."+dataField);
                            queryFieldList.add("(select ct.SHOWVALUE from ctp_enum_item ct where ct.ID = "+bm+"."+dataField+") "+dataField+"_name");
                        }
                        queryFieldList.add(bm+"."+dataField);
                        querFieldMapList.put(bmOwnerTableName,queryFieldList);

                    }else{
                        if(titleSp[2].equals("1")){
//                            queryFieldList.add("ct"+tableIndex+".SHOWVALUE "+dataField+"_name"+"- left join ctp_enum_item ct"+tableIndex+" on ct"+tableIndex+".ID = tb"+tableIndex+"."+dataField);
                            queryFieldList.add("(select ct.SHOWVALUE from ctp_enum_item ct where ct.ID = "+bm+"."+dataField+") "+dataField+"_name");
                        }
                        queryFieldList.add(bm+"."+dataField);
                    }
                }else{
                    ArrayList<String> queryFieldList = new ArrayList<String>();
                    //添加id
//                    if(tableName.equals(ownerTableName)){
                    queryFieldList.add("tb"+tableIndex+".id tb"+tableIndex+"id");
                    unquidStr.add("tb"+tableIndex+"id");
//                        queryFieldList.add("tb"+tableIndex+".id");
//                    }
                    if(titleSp[2].equals("1")){
//                        queryFieldList.add("ct"+tableIndex+".SHOWVALUE "+dataField+"_name"+"- left join ctp_enum_item ct"+tableIndex+" on ct"+tableIndex+".ID = tb"+tableIndex+"."+dataField);
                        queryFieldList.add("(select ct.SHOWVALUE from ctp_enum_item ct where ct.ID = tb"+tableIndex+"."+dataField+") "+dataField+"_name");
                    }
                    queryFieldList.add("tb"+tableIndex+"."+dataField);
                    querFieldMapList.put(bmOwnerTableName,queryFieldList);
                }
            }

            //查询字段
            StringBuilder querySql = new StringBuilder("select ");
            for (String s : querFieldMapList.keySet()) {
                for (String s1 : querFieldMapList.get(s)) {
                    String[] split = s1.split("-");
                    querySql.append(split[0]+",");
                }
            }

            //添加查询表
            StringBuilder queryConditionSql = new StringBuilder(" from ");
            for (String s : querFieldMapList.keySet()) {
                queryConditionSql.append(s+",");
            }
            queryConditionSql = new StringBuilder(queryConditionSql.substring(0, queryConditionSql.length() - 1));

            //添加查询条件
            StringBuilder queryWhereSql = new StringBuilder(" where 1 = 1 ");

            //添加明细表查询条件
            for (String s : querFieldMapList.keySet()) {
                String formmain = querFieldMapList.keySet().stream().filter(s2 -> s2.contains("formmain")).collect(Collectors.toList()).get(0);
                String[] formmainsp = formmain.split(" ");
                String[] fommsonsp = s.split(" ");
                if(s.contains("formson")){
                    queryWhereSql.append(" and " + fommsonsp[1]+".formmain_id = "+formmainsp[1]+".ID");
                }
            }

            String sql = querySql.substring(0,querySql.length()-1)+queryConditionSql+queryWhereSql;
            queryWhereSql = new StringBuilder("select * from ("+sql+") b where 1=1 ");

            //添加扩展查询字段
            if(null != extendFieldQueryList && !extendFieldQueryList.isEmpty()){
                for (Map<String, Object> map : extendFieldQueryList) {
                    String[] titleSp = StrKit.str(map.get("title")).split("-");
                    String queryField = "";
                    if(titleSp[2].equals("1")){
                        queryField = StrKit.str(map.get("dataField"))+"_name";
                    }else{
                        queryField = StrKit.str(map.get("dataField"));
                    }
                    String dataFieldValue = StrKit.str(map.get("dataFieldValue"));
                    if(dataFieldValue.contains("%")){
                        dataFieldValue = " like('"+dataFieldValue+"')";
                    }else if(dataFieldValue.contains("in(")){
                        dataFieldValue = " "+dataFieldValue;
                    }else{
                        dataFieldValue = " = '"+dataFieldValue+"'";
                    }
                    queryWhereSql.append(" and "+queryField+dataFieldValue);
                }
            }

            //添加查询条件
            if(parm != null){
                for (String s : parm.keySet()) {
                    String value = StrKit.str(parm.get(s));
                    if(!value.equals("")){
                        queryWhereSql.append(" and "+s+" like('%"+value+"%')");
                    }
                }
            }

            String sql2 = queryWhereSql.toString();
            log.info("二级明细扩展，获取选择列表数据表数据查询Sql："+sql2);
            try {
                List<Map<String, Object>> maps = DBKit.excuteSQL(sql2, null);
                reualList = maps;
            } catch (Exception e) {
                log.info("二级明细扩展，获取选择列表数据表数据查询异常：",e);
            }
            //拼装唯一值
            if(!unquidStr.isEmpty()){
                for (Map<String, Object> map : reualList) {
                    String unidStr = "";
                    for (String s : unquidStr) {
                        String str = StrKit.str(map.get(s));
                        unidStr+=str+"_";
                    }
                    map.put("id",unidStr);
                }
            }
        }
        return reualList;
    }


    /**
     * 保存二级明细数据
     * @param pramMap
     * @return
     */
    public Map<String,Object> saveSencondDatail(Map<String,Object> pramMap){
        HashMap<String, Object> resualtMap = new HashMap<>();
        SencondDatailPO sencondDatailPO = new SencondDatailPO();
        String masterId = StrKit.str(pramMap.get("masterId"));
        String recordId = StrKit.str(pramMap.get("recordId"));
        HashMap<String, Object> qyerMap = new HashMap<>();
        qyerMap.put("masterId",masterId);
        qyerMap.put("recordId",recordId);
        //判断是否已经存在存在就删除原有的数据
        List<SencondDatailPO> datasByMap = sencondDatailManager.findDatasByMap(qyerMap);
        for (SencondDatailPO datailPO : datasByMap) {
            DBAgent.delete(datailPO);
        }

        List<Map<String,Object>> sencondDataList = (List<Map<String,Object>>)pramMap.get("sencondData");
        sencondDatailPO.setIdIfNew();
        sencondDatailPO.setSencondData(JSONObject.toJSONString(sencondDataList));
        sencondDatailPO.setMasterId(masterId);
        sencondDatailPO.setRecordId(recordId);
        try {
            sencondDatailManager.save(sencondDatailPO);
            resualtMap.put("code","200");
            resualtMap.put("msg",null);
        }catch (Exception e){
            resualtMap.put("code","500");
            resualtMap.put("msg","保存数据异常，请检查！！！！！");
        }
        return resualtMap;
    }


    /**
     * 查询二级明细数据
     * @param pramMap
     * @return
     */
    public List<Map<String,Object>> getSencondDatail(Map<String,Object> pramMap){
        List<Map<String, Object>> maps = new ArrayList<>();
        List<SencondDatailPO> datasByMap = sencondDatailManager.findDatasByMap(pramMap);
        for (SencondDatailPO sencondDatailPO : datasByMap) {
            String sencondData = sencondDatailPO.getSencondData();
            List<Map<String,Object>> dataList = JSONObject.parseObject(sencondData, List.class);
            maps.addAll(dataList);
        }
        return maps;
    }


    /**
     * 回写二级明细表数据
     * @param masterId
     * @param formTempCode
     */
    public void saveTableSencondDatail(String masterId,String formTempCode){
        HashMap<String, Object> queryMap = new HashMap<>();
        queryMap.put("masterId",masterId);
        List<SencondDatailPO> datasByMap = sencondDatailManager.findDatasByMap(queryMap);
        FormBean formBean = null;
        try {
            formBean = cap4FormManager.getFormByFormCode(formTempCode);
        } catch (BusinessException e) {
            log.info("扩展二级明细，回写表单二级明细异常：",e);
        }
        if(formBean != null){
            FormDataMasterBean dataMasterBean = null;
            try {
                dataMasterBean = cap4FormManager.getDataMasterBeanById(Long.parseLong(masterId), formBean, null);
            } catch (Exception e) {
                log.info("扩展二级明细，回写表单二级明细，获取表数据异常：",e);
            }
            if(dataMasterBean != null){
                //获取配置文件信息
                Map<String, Object> configSecondDetil = getConfigSecondDetil();
                List<Map<String,Object>> fieldList = (List<Map<String,Object>>)configSecondDetil.get("fieldListString");
                String dataSubTableName = StrKit.str(configSecondDetil.get("dataSubTableName"));
                String hxDataSubTableName = StrKit.str(configSecondDetil.get("hxDataSubTableName"));

                //获取来源表单字段信息
                List<FormTableBean> lySubTableList = formBean.getSubTableBean().stream().filter(f -> f.getTableName().equals(dataSubTableName)).collect(Collectors.toList());
                FormTableBean lySubTable = null;
                if(!lySubTableList.isEmpty()){
                    lySubTable = lySubTableList.get(0);
                }
                //获取回写目标表单字段信息
                List<FormTableBean> mbSubTableList = formBean.getSubTableBean().stream().filter(f -> f.getTableName().equals(hxDataSubTableName)).collect(Collectors.toList());
                FormTableBean mbSubTable = null;
                if(!mbSubTableList.isEmpty()){
                    mbSubTable = mbSubTableList.get(0);
                }
                if(lySubTable == null || mbSubTable == null){
                    log.info("回写二级明细表数据，获取表单为null，获取的来源表为："+dataSubTableName+"，获取的目标表为："+hxDataSubTableName);
                    return;
                }
                //删除原有的目标明细表数据
                ArrayList<Long> longs = new ArrayList<>();
                for (FormDataSubBean subDatum : dataMasterBean.getSubData(hxDataSubTableName)) {
                    longs.add(subDatum.getId());
                }
                try {
                    dataMasterBean.removeSubData(hxDataSubTableName,longs);
                } catch (BusinessException e) {
                    log.info("回写二级明细表数据，删除数据异常！！！！",e);
                    return;
                }
                //获取明细表数据
                int groupSort = 1;
                List<FormDataSubBean> formDataSubBeans = new ArrayList<>();
                for (FormDataSubBean subDatum : dataMasterBean.getSubData(dataSubTableName)) {
                    //获取对应的二级明细数据
                    List<SencondDatailPO> collect = datasByMap.stream().filter(d -> d.getRecordId().equals(StrKit.str(subDatum.getId()))).collect(Collectors.toList());
                    //获取原本有值的字段
                    HashMap<String, Object> fieldDataMap = new HashMap<>();
                    for (FormFieldBean field : lySubTable.getFields()) {
                        String fieldValue = StrKit.str(subDatum.getFieldValue(field.getName()));
                        if(!fieldValue.equals("")){
                            fieldDataMap.put(field.getDisplay(),fieldValue);
                        }
                    }

                    if(collect.isEmpty()){
                        //将有值的字段写入目标明细表中去
                        FormDataSubBean formDataSubBean = new FormDataSubBean(mbSubTable,dataMasterBean);
                        formDataSubBean.setGroupSort(groupSort);
                        //添加原本字段值
                        for (String s : fieldDataMap.keySet()) {
                            List<FormFieldBean> mbFieldList = mbSubTable.getFields().stream().filter(m -> m.getDisplay().split("_")[0].equals(s.split("_")[0])).collect(Collectors.toList());
                            if(!mbFieldList.isEmpty()){
                                FormFieldBean formFieldBean = mbFieldList.get(0);
                                formDataSubBean.addFieldValue(formFieldBean.getName(),fieldDataMap.get(s));
                            }
                        }
                        formDataSubBean.setSort(1);
                        formDataSubBeans.add(formDataSubBean);
                    }else{
                        //添加扩展字段值
                        for (SencondDatailPO sencondDatailPO : collect) {
                            String sencondData = sencondDatailPO.getSencondData();
                            //获取二级明细扩展数据
                            List<Map<String,Object>> mapList = JSONObject.parseObject(sencondData, List.class);
                            int sort = 1;
                            for (Map<String, Object> map : mapList) {
                                //将有值的字段写入目标明细表中去
                                FormDataSubBean formDataSubBean = new FormDataSubBean(mbSubTable,dataMasterBean);
                                formDataSubBean.setGroupSort(groupSort);
                                //添加原本字段值
                                for (String s : fieldDataMap.keySet()) {
                                    List<FormFieldBean> mbFieldList = mbSubTable.getFields().stream().filter(m -> m.getDisplay().split("_")[0].equals(s.split("_")[0])).collect(Collectors.toList());
                                    if(!mbFieldList.isEmpty()){
                                        FormFieldBean formFieldBean = mbFieldList.get(0);
                                        formDataSubBean.addFieldValue(formFieldBean.getName(),fieldDataMap.get(s));
                                    }
                                }

                                for (String s : map.keySet()) {
                                    List<Map<String, Object>> fieldMps = fieldList.stream().filter(f -> StrKit.str(f.get("title")).split("-")[1].equals(s)).collect(Collectors.toList());
                                    if(!fieldMps.isEmpty()){
                                        Map<String, Object> map1 = fieldMps.get(0);
                                        String writeBackField = StrKit.str(map1.get("writeBackField"));
                                        formDataSubBean.addFieldValue(writeBackField,map.get(s));
                                    }
                                }
                                formDataSubBean.setSort(sort);
                                formDataSubBeans.add(formDataSubBean);
                                sort++;
                            }
                        }
                    }
                    //添加二级明细表数据
                    dataMasterBean.addSubDatas(hxDataSubTableName,formDataSubBeans,null);
                    groupSort++;
                }
                //保存数据
                try {
                    cap4FormManager.saveOrUpdateFormData(dataMasterBean,formBean.getId(),true);
                    log.info("二级明细扩展数据保存成功");
                } catch (Exception e) {
                    log.info("二级明细扩展数据保存异常：",e);
                }
            }
        }
    }


    /**
     * 获取筛选条件字段
     * @return
     */
    public List<Map<String,Object>> getQueryField(){
        Map<String, Object> configSecondDetil = getConfigSecondDetil();
        List<Map<String,Object>> fieldList = (List<Map<String,Object>>)configSecondDetil.get("queryField");
        return fieldList;
    }


    /**
     * 获取需要回写到表单数据的字段
     * @return
     */
    public List<Map<String,Object>> getWriteBackField(){
        Map<String, Object> configSecondDetil = getConfigSecondDetil();
        List<Map<String,Object>> fieldList = (List<Map<String,Object>>)configSecondDetil.get("fieldListString");
        List<Map<String,Object>> dataFieldMaps = new ArrayList<>();
        for (Map<String, Object> map : fieldList) {
            String jsHxField = StrKit.str(map.get("jsHxField"));
            if(jsHxField.equals("")){
                continue;
            }
            HashMap<String, Object> fieldMap = new HashMap<>();
            fieldMap.put("dataField",StrKit.str(map.get("dataField")));
            fieldMap.put("jsHxField",StrKit.str(map.get("jsHxField")));
            dataFieldMaps.add(fieldMap);
        }
        return dataFieldMaps;
    }


    /**
     * 获取配置文件数据
     * @return
     */
    private Map<String,Object> getConfigSecondDetil(){
        try {
            //获取配置文件地址
            String confgFildPah = "apps_res/cap/customCtrlResources/secondDetailTableResources/configSecond/configSecondDetail.txt";
            //获取配置文件文件目录
            String filePath = AppContext.getCfgHome().getCanonicalPath();
            filePath = filePath.replace("WEB-INF" + File.separator + "cfgHome", confgFildPah);
            byte[] bytes = Files.readAllBytes(Paths.get(filePath));
            String value = new String(bytes, StandardCharsets.UTF_8);
            Map<String,Object> map = JSONObject.parseObject(value,Map.class);
            return map;
        }catch (Exception e){
            log.info("获取二级明细扩展字段配置异常：",e);
            return null;
        }
    }
}
